<?php
/*******************************************************************************
* $Date:: May 30, 2011 7:37:59 AM                                             $
* $Revision:                                                                  $
* $Author:: Tuan Duong                                                        $
* $Comment::                                                                  $
******************************************************************************/ 

/**
* Description here...
*
* @author	Tuan Duong <duongthaso[at]gmail[dot]com>
* @version 
*/

class Sss_Table_Abstract extends Zend_Db_Table_Abstract 
{
	static protected $initializedUtf8; 
	protected $_db_ovis_name     = OVIS_DATABASE;
	protected $_db_shepherd_name = SHEPHERD_SUFIX;  
	public function __construct()
	{
		parent::__construct();
		if (!self::$initializedUtf8) {
			$this->getDefaultAdapter()->query("SET NAMES 'utf8'");
			self::$initializedUtf8 = true;
		}
	}

	public function setTableName($tableName)
	{
		$this->_name = (string)$tableName;
		return $this;
	}

	protected function getTableName() 
	{
		return $this->_name;	
	}

	private static $_currentHandleName = '';
	public function setCurrentHandleName($value)
	{
		Sss_Table_Abstract::$_currentHandleName = $value;
	}

	protected function getCurrentShepherdSchema($instanceId=null)
	{
		if (is_null($instanceId)) {
			$defaultNamespace = new Zend_Session_Namespace(Sss_Ultility_SessionName::SHEPHERD_SYSTEM . Sss_Table_Abstract::$_currentHandleName );
			$handleSession = new Zend_Session_Namespace(Sss_Ultility_SessionName::HANDLE_SESSION . Sss_Table_Abstract::$_currentHandleName );
			$defaultNamespaceOvis = new Zend_Session_Namespace(Sss_Ultility_SessionName::OVIS_SHEPHERD_SYSTEM . Sss_Table_Abstract::$_currentHandleName );
			if($handleSession->handle == Sss_Ultility_CommonViewParamater::UNDERFINE){
				if(isset($defaultNamespaceOvis->dbShepherd)){
					return SHEPHERD_SUFIX.Sss_Ultility_Common::formatString($defaultNamespaceOvis->dbShepherd,Sss_Ultility_Setting::FORMAT_NUMBER);
				} else {
					return SHEPHERD_SUFIX.Sss_Ultility_Common::formatString($defaultNamespace->dbShepherd,Sss_Ultility_Setting::FORMAT_NUMBER);
				}
			} else {
				if(isset($defaultNamespace->dbShepherd)){
					return SHEPHERD_SUFIX.Sss_Ultility_Common::formatString($defaultNamespace->dbShepherd,Sss_Ultility_Setting::FORMAT_NUMBER);
				}
			}
			return SHEPHERD_SUFIX.Sss_Ultility_Common::formatString(Sss_Ultility_Setting::DATABASE_DEFAULT,Sss_Ultility_Setting::FORMAT_NUMBER);
		} else {
			return SHEPHERD_SUFIX.Sss_Ultility_Common::formatString($instanceId,Sss_Ultility_Setting::FORMAT_NUMBER);
		}
	}

	private function _getShepherdAdapter($instanceId=null)
	{
		$config = new Zend_Config_Ini( APPLICATION_PATH . '/configs/application.ini', 'production');
		$db = new Zend_Db_Adapter_Pdo_Mysql(array(
				'host'     => $config->resources->db->params->host,
				'username' => $config->resources->db->params->username,
				'password' => $config->resources->db->params->password,
				'dbname'   => $this->getCurrentShepherdSchema(Sss_Ultility_Common::formatString($instanceId,Sss_Ultility_Setting::FORMAT_NUMBER))
		));
		return $db;
	}

	/**
	* Find all rows in table with $query string
	* @param string|string query
	* @return array
	*/
	public function loadAll($query=null, $dbShepherd=false, $instanceId=null) 
	{
		$defaultNamespace = new Zend_Session_Namespace(Sss_Ultility_SessionName::SHEPHERD_SYSTEM . Sss_Table_Abstract::$_currentHandleName);
		try {
			if($dbShepherd) {
				if($instanceId == null){
					$defaultNamespace = new Zend_Session_Namespace(Sss_Ultility_SessionName::SHEPHERD_SYSTEM . Sss_Table_Abstract::$_currentHandleName);   
					$instanceId =  $defaultNamespace->dbShepherd;
					if($instanceId == null) {
						$instanceId = Sss_Ultility_Setting::DATABASE_DEFAULT;
					}
				}
				$dbAdapter = $this->_getShepherdAdapter(Sss_Ultility_Common::formatString($instanceId, Sss_Ultility_Setting::FORMAT_NUMBER));
			} else {
				$dbAdapter = $this->getDefaultAdapter();  
			}
			$result=$dbAdapter->query($query)->fetchAll();
			$dbAdapter->closeConnection();
		} catch (Exception $e) {
			Sss_Ultility_Common::logger()->log($e, Zend_Log::ERR);
			$dbAdapter->rollBack();
			$dbAdapter->closeConnection();
			throw new Sss_Exception_Abstract($e->getMessage());
		}
		return $result;
	}
	/**
	* Get an row in database
	* @param string|string query
	* @return object
	*/
	public function fetchObject($query=null, $dbShepherd=false, $instanceId=null) 
	{
		try {
			if($dbShepherd)
			{
				if($instanceId == null){
					$defaultNamespace = new Zend_Session_Namespace(Sss_Ultility_SessionName::SHEPHERD_SYSTEM . Sss_Table_Abstract::$_currentHandleName);   
					$instanceId =  $defaultNamespace->dbShepherd;
					if($instanceId == null) {
						$instanceId = Sss_Ultility_Setting::DATABASE_DEFAULT;
					}
				}
				$dbAdapter = $this->_getShepherdAdapter(Sss_Ultility_Common::formatString($instanceId, Sss_Ultility_Setting::FORMAT_NUMBER)); 
			} else {
				$dbAdapter = $this->getDefaultAdapter();  
			}
			$result=$dbAdapter->query($query)->fetchObject();
			$dbAdapter->closeConnection();
		} catch (Exception $e) {
			Sss_Ultility_Common::logger()->log($e, Zend_Log::ERR);
			$dbAdapter->rollBack();
			$dbAdapter->closeConnection();
			throw new Sss_Exception_Abstract($e->getMessage());
		}
		return $result;
	}

	/**
	* Insert data to table
	* @param array|string  
	* @return boolean
	*/
	function insertData(array $arrData, $dbShepherd=false, $instanceId=null)
	{
		if($dbShepherd)
		{
			if($instanceId == null){
				$defaultNamespace = new Zend_Session_Namespace(Sss_Ultility_SessionName::SHEPHERD_SYSTEM . Sss_Table_Abstract::$_currentHandleName);   
				$instanceId =  $defaultNamespace->dbShepherd;
			}
			$dbAdapter = $this->_getShepherdAdapter(Sss_Ultility_Common::formatString($instanceId,Sss_Ultility_Setting::FORMAT_NUMBER));   
		}
		else
		{
			$dbAdapter = $this->getDefaultAdapter();  
		}

		$dbAdapter->beginTransaction();
		try {            
			$dbAdapter->insert($this->_name, $arrData);
			$id=$dbAdapter->lastInsertId();
			$dbAdapter->commit();
			$dbAdapter->closeConnection();
		} catch (Exception $e) {
			Sss_Ultility_Common::logger()->log($e, Zend_Log::ERR);
			$dbAdapter->rollBack();
			$dbAdapter->closeConnection();
			throw new Sss_Exception_Abstract($e->getMessage());
		}        
		return $id;
	}

	/**
	* update data to table
	* @param array|string  
	* @return boolean
	*/
	function updateData(array $arrId, array $arrData, $dbShepherd=false, $instanceId=null)
	{	
		$arrwhere = array();
		foreach($arrId as $k=>$value)
		{ 
			if(!(int)$value)
				$arrwhere[] = $k."='".$value."'";
			else
				$arrwhere[] = $k."=".$value;
		}
		if($dbShepherd)
		{
			if($instanceId == null){
				$defaultNamespace = new Zend_Session_Namespace(Sss_Ultility_SessionName::SHEPHERD_SYSTEM . Sss_Table_Abstract::$_currentHandleName);   
				$instanceId =  $defaultNamespace->dbShepherd;
			}
			$dbAdapter = $this->_getShepherdAdapter(Sss_Ultility_Common::formatString($instanceId,Sss_Ultility_Setting::FORMAT_NUMBER));   
		}
		else
		{
			$dbAdapter = $this->getDefaultAdapter();  
		}
		$arrwhere   = count($arrwhere) ? implode(' AND ', $arrwhere) : '';
		$dbAdapter->beginTransaction();
		$result = false;
		try {
			$result = $this->update($arrData, $arrwhere);
			$dbAdapter->commit();
			$dbAdapter->closeConnection();
		} catch (Exception $e) {
			Sss_Ultility_Common::logger()->log($e, Zend_Log::ERR);
			$dbAdapter->rollBack();
			$dbAdapter->closeConnection();
			throw new Sss_Exception_Abstract($e->getMessage());
		}
		return $result;
	}

	function findEntityById(array $arrId, $dbShepherd=false)
	{
		$defaultNamespace = new Zend_Session_Namespace(Sss_Ultility_SessionName::SHEPHERD_SYSTEM . Sss_Table_Abstract::$_currentHandleName);   

		try {
			$keyName = '';
			$keyValue = '';
			foreach($arrId as $k=>$value)
			{
				$keyName = $k;
				$keyValue = $value;    
			}
			if($dbShepherd)
			{
				$dbAdapter = $this->_getShepherdAdapter($defaultNamespace->dbShepherd);   
			}
			else
			{
				$dbAdapter = $this->getDefaultAdapter();  
			}

			$select = $dbAdapter->select()
			->from($this->getTableName())
			->where($keyName.'=?', $keyValue);
			$result = $select->query()->fetchObject();
			$dbAdapter->closeConnection();
		} catch (Exception $e) {
			Sss_Ultility_Common::logger()->log($e, Zend_Log::ERR);
			$dbAdapter->rollBack();
			$dbAdapter->closeConnection();
			throw new Sss_Exception_Abstract($e->getMessage());  
		}
		return $result;    
	}

	/**
	* Delete record from table
	* @param string|string  
	* @return boolean
	*/
	function deleteRecord(array $where, $dbShepherd, $instanceId=null)
	{
		$arrwhere = array();
		foreach($where as $k=>$value)
		{ 
			if(!(int)$value)
				$arrwhere[] = $k."='".$value."'";
			else
				$arrwhere[] = $k."=".$value;
		}
		if($dbShepherd)
		{
			if($instanceId == null){
				$defaultNamespace = new Zend_Session_Namespace(Sss_Ultility_SessionName::SHEPHERD_SYSTEM . Sss_Table_Abstract::$_currentHandleName);   
				$instanceId =  $defaultNamespace->dbShepherd;
			}
			$dbAdapter = $this->_getShepherdAdapter(Sss_Ultility_Common::formatString($instanceId,Sss_Ultility_Setting::FORMAT_NUMBER));   
		}
		else
		{
			$dbAdapter = $this->getDefaultAdapter();  
		}
		$arrwhere   = count($arrwhere) ? implode(' AND ', $arrwhere) : '';
		$dbAdapter->beginTransaction();
		$result = false;
		try{
			$result = $dbAdapter->delete($this->getTableName(), $arrwhere);
			$dbAdapter->commit();
			$dbAdapter->closeConnection();            
		}
		catch(Exception $e)
		{
			Sss_Ultility_Common::logger()->log($e, Zend_Log::ERR);
			$dbAdapter->rollBack();
			$dbAdapter->closeConnection();
			throw new Sss_Exception_Abstract($e->getMessage());  
		}
		return $result;
	}

	public function executeQuery($query=null, $dbShepherd=false, $instanceId=null) 
	{
		try {
			if($dbShepherd) {
				if($instanceId == null){
					$defaultNamespace = new Zend_Session_Namespace(Sss_Ultility_SessionName::SHEPHERD_SYSTEM . Sss_Table_Abstract::$_currentHandleName);   
					$instanceId =  $defaultNamespace->dbShepherd;
					if($instanceId == null){
						$instanceId = Sss_Ultility_Setting::DATABASE_DEFAULT;
					}
				}
				$dbAdapter = $this->_getShepherdAdapter(Sss_Ultility_Common::formatString($instanceId,Sss_Ultility_Setting::FORMAT_NUMBER));   
			} else {
				$dbAdapter = $this->getDefaultAdapter();  
			}
			$result=$dbAdapter->exec($query);
			$dbAdapter->closeConnection();
		} catch (Exception $e) {
			Sss_Ultility_Common::logger()->log($e, Zend_Log::ERR);
			$dbAdapter->rollBack();
			$dbAdapter->closeConnection();
			throw new Sss_Exception_Abstract($e->getMessage());  
		}
		return $result;
	}

	/**
	* Returns the column/value data as an array.
	*
	* @return array
	*/
	public function toArray()
	{
		return (array)$this->_data;
	}

	public function checkExistedShepherdDatabase($instanceId)
	{
		if($instanceId == null || $instanceId == ''){
			$defaultNamespace = new Zend_Session_Namespace(Sss_Ultility_SessionName::SHEPHERD_SYSTEM . Sss_Table_Abstract::$_currentHandleName);   
			$instanceId =  $defaultNamespace->dbShepherd;
		}
		$checkSQL = "SELECT SCHEMA_NAME FROM INFORMATION_SCHEMA.SCHEMATA WHERE SCHEMA_NAME = '".SHEPHERD_SUFIX . Sss_Ultility_Common::formatString($instanceId,Sss_Ultility_Setting::FORMAT_NUMBER) . "'";
		$res = $this->fetchObject($checkSQL);
		if (!$res) {
			return false;
		}
		return true;
	}
}
